////////////////////////////////////////////////////////////////////////////////
// This file is part of the Mist compiler.                                    //
//                                                                            //
// Copyright (C) 2008, 2009 The Mist project                                  //
//                                                                            //
// For a list of contributors, see the COMMITTERS file.                       //
//                                                                            //
// The Mist compiler is free software: you can redistribute it and/or modify  //
// it under the terms of the GNU General Public License as published by       //
// the Free Software Foundation, either version 3 of the License, or          //
// (at your option) any later version.                                        //
//                                                                            //
// The Mist compiler is distributed in the hope that it will be useful,       //
// but WITHOUT ANY WARRANTY; without even the implied warranty of             //
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the              //
// GNU General Public License for more details.                               //
//                                                                            //
// You should have received a copy of the GNU General Public License          //
// in the COPYING file. If not, see <http://www.gnu.org/licenses/>.           //
////////////////////////////////////////////////////////////////////////////////

///
/// \file
/// Contains the Messages class.
///

#ifndef MESSAGES_HPP
#define MESSAGES_HPP

////////////////////////////////////////////////////////////////////////////////
// Includes                                                                   //
////////////////////////////////////////////////////////////////////////////////

#include <set>
using std::set;

#include <ostream>
using std::ostream;

#include <boost/range.hpp>

#include "message.hpp"
#include "common/outputproducer.hpp"
#include "common/types.hpp"
#include "common/ptr.hpp"

////////////////////////////////////////////////////////////////////////////////
// Messages Class                                                             //
////////////////////////////////////////////////////////////////////////////////

/// A class used to collect compiler messages.
///
class Messages : public OutputProducer {
	public:
		
		/// Add \a message to this set of messages.
		///
		void add(sptr<Message> message);
		
		/// Add a message with code \a code and without location to this set of messages.
		///
		void add(const string& code);
		
		/// Add a message with code \a code and without location but with a parameter to this set of messages.
		///
		void add(const string& code, const string& param1);
		
		/// Add a message with code \a code and without location but two parameters to this set of messages.
		///
		void add(const string& code, const string& param1, const string& param2);
		
		/// Add a message with code \a code and without location but three parameters to this set of messages.
		///
		void add(const string& code, const string& param1, const string& param2, const string& param3);
		
		/// Add a message with code \a code and location \a location to this set of messages.
		///
		void add(const string& code, const Location& location);
		
		/// Add a message with code \a code, location \a location and a parameter to this set of messages.
		///
		void add(const string& code, const Location& location, const string& param1);
		
		/// Add a message with code \a code, location \a location and two parameters to this set of messages.
		///
		void add(const string& code, const Location& location, const string& param1, const string& param2);
		
		/// Add a message with code \a code, location \a location and three parameters to this set of messages.
		///
		void add(const string& code, const Location& location, const string& param1, const string& param2, const string& param3);
		
		/// \return the number of collected messages
		///
		uint count() const;
		
		/// \return the number of messages of a given \a severity
		///
		uint count(MessageSeverity severity) const;
		
		/// \return the number of messages with a given \a code
		///
		uint count(const string& code) const;
		
		/// Send a sorted list of all collected messages to output-stream \a out.
		///
		/// \return the stream \a out
		///
		ostream& send_to_stream(ostream& out) const;
	
	private:
		
		vector<sptr<Message> > _messages;
};

#endif // MESSAGES_HPP
